const { src, dest, parallel, series, watch } = require('gulp')

const del = require('del')
const browserSync = require('browser-sync')//不是gulp插件，所以得单独引用

const loadPlugins = require('gulp-load-plugins')//加载全部plugins gulp-会删除，剩下的会驼峰命名

const plugins = loadPlugins()
const bs = browserSync.create()
const cwd=process.cwd()//返回当前命令行的工作目录
let config={
  //默认config
  build:{
    src:'src',
    dist:'dist',
    temp:'temp',
    public: 'public',
    paths:{
      styles: 'assets/styles/*.scss',
      scripts: 'assets/scripts/*.js',
      pages: '*.html',
      images: 'assets/images/**',
      fonts: 'assets/fonts/**'
    }
  }
}
try{
  const loadConfig=require(`${cwd}/pages.config.js`)
  config=Object.assign({},config,loadConfig)
}catch(e){

}
const clean = () => {
  return del([config.build.dist, config.build.temp])
}
//....................src
const style = () => {//样式
  return src(config.build.paths.styles, { base: config.build.src,cwd:config.build.src })//保留原始目录结构
    .pipe(plugins.sass({ outputStyle: 'expanded' }))//输出方式：完全展开
    .pipe(dest(config.build.temp))//temp临时目录
    .pipe(bs.reload({ stream: true }))
}

const script = () => {//脚本
  return src(config.build.paths.scripts, { base: config.build.src,cwd:config.build.src })
    .pipe(plugins.babel({ presets: [require('@babel/preset-env')] }))
    .pipe(dest(config.build.temp))
    .pipe(bs.reload({ stream: true }))
}

const page = () => {//模板文件
  return src(config.build.paths.pages, { base: config.build.src,cwd:config.build.src })
    .pipe(plugins.swig({ data:config.data, defaults: { cache: false } })) // 防止模板缓存导致页面不能及时更新
    .pipe(dest(config.build.temp))
    .pipe(bs.reload({ stream: true }))
}
//压缩 图片 字体
const image = () => {
  return src(config.build.paths.images, { base: config.build.src,cwd:config.build.src })
    .pipe(plugins.imagemin())
    .pipe(dest(config.build.dist))
}

const font = () => {
  return src(config.build.paths.fonts, { base: config.build.src,cwd:config.build.src })
    .pipe(plugins.imagemin())
    .pipe(dest(config.build.dist))
}
//....................public
const extra = () => {
  return src('**', { base: config.build.public,cwd:config.build.public })
    .pipe(dest(config.build.dist))
}

const serve = () => {
  //......................监视变化
  watch(config.build.paths.styles,{cwd:config.build.paths.styles}, style)
  watch(config.build.paths.scripts,{cwd:config.build.paths.scripts}, script)
  watch(config.build.paths.pages,{cwd:config.build.paths.pages}, page)
  // watch('src/assets/images/**', image)
  // watch('src/assets/fonts/**', font)
  // watch('public/**', extra)
  watch([
    config.build.paths.images,
    config.build.paths.fonts,
  ], {cwd:config.build.src},bs.reload)
  watch('**',{cwd:config.build.public},bs.reload)
//....................开发服务器
  bs.init({
    notify: false,//关掉提示
    port: 2080,
    // open: false,// 取消自动打开
    // files: 'dist/**',// 指定监听文件，同bs.reload
    server: {
      baseDir: [config.build.temp, config.build.src, config.build.public],
      routes: {
        '/node_modules': 'node_modules'
      }
    }
  })
} //与最终上线的文件 dist 无关

const useref = () => {//使用关系，合并构建引入的资源
  return src(config.build.paths.pages, { base: config.build.temp,cwd:config.build.temp })
    .pipe(plugins.useref({ searchPath: [config.build.temp, '.'] }))
    // html js css
    .pipe(plugins.if(/\.js$/, plugins.uglify()))
    .pipe(plugins.if(/\.css$/, plugins.cleanCss()))
    .pipe(plugins.if(/\.html$/, plugins.htmlmin({
      collapseWhitespace: true,
      minifyCSS: true,
      minifyJS: true
    })))
    .pipe(dest(config.build.dist))
}

const compile = parallel(style, script, page)//开发阶段不需要压缩image、font

// 上线之前执行的任务
const build =  series(
  clean,
  parallel(
    series(compile, useref),
    image,
    font,
    extra
  )
)
//开发阶段
const develop = series(compile, serve)

module.exports = {
  clean,
  build,
  develop
}
